<?php
declare (strict_types=1);

namespace app\api\controller\v1;

use app\api\helpers\Tree;
use app\api\helpers\v1\traits\SearchDataForModel;
use app\api\model\v1\AdminLog;
use app\api\model\v1\AuthGroup;
use app\api\model\v1\EveryDayAnswerCensus;
use app\api\model\v1\Exam;
use app\api\model\v1\ExamDetail;
use app\api\model\v1\ExamSecondLevel;
use app\api\model\v1\ExamStairType;
use app\api\model\v1\NotUploadQuestion;
use app\api\model\v1\NotUploadQuestionLog;
use app\api\model\v1\OperateUserLog;
use app\api\model\v1\Template;
use app\api\model\v1\TemplateDetail;
use app\api\model\v1\TemplateSecondLevel;
use app\api\model\v1\TemplateType;
use app\api\model\v1\TopicUserDay;
use app\api\model\v1\TopicUserDaySync;
use app\api\model\v1\UnitTotal;
use app\api\model\v1\Users;
use app\BaseController;
use think\Request;

class ExamCon extends BaseController
{

    use SearchDataForModel;

    /**
     * @User: 刘海龙
     * @Date: 2021/9/27
     * @Time: 8:38
     * @return \think\response\Json
     * @throws \think\db\exception\DbException
     * 问卷列表
     */
    public function getExamList()
    {
        $limit = $this->request->param('limit', 10);
        $res = Exam::with(['unit', 'industry'])->where([['create_id', 'in', $this->childrenAdminIds]])->paginate($limit)->each(function ($item, $key) {
            $item['exam_type_name'] = Exam::$is_exam_type[$item['exam_type']];
            $item['status_name'] = Exam::$is_status[$item['status']];
            $item['exam_creation_type_name'] = Exam::$exam_creation_type[$item['exam_creation_type']];
            $item['is_release_name'] = Exam::$is_release[$item['is_release']];
            return $item;
        });
        return $this->response($res);
    }

    /**
     * @param $id
     * @User: 刘海龙
     * @Date: 2021/9/27
     * @Time: 11:15
     * @return \think\response\Json
     * @throws \think\db\exception\DataNotFoundException
     * @throws \think\db\exception\DbException
     * @throws \think\db\exception\ModelNotFoundException
     * 根据问卷id 获取对应的一级菜单和二级菜单
     */
    public function getExamShow($id)
    {
        $exam = Exam::with(['examStairType' => ['examSecondLevel'], 'template'])->find(intval($id));
        if (is_null($exam)) {
            return $this->response(403, '暂未找到该问卷');
        }
        return $this->response($exam);
    }

    /**
     * @User: 刘海龙
     * @Date: 2021/9/27
     * @Time: 11:58
     * @return \think\response\Json
     * @throws \think\db\exception\DataNotFoundException
     * @throws \think\db\exception\DbException
     * @throws \think\db\exception\ModelNotFoundException
     * 新增并返回
     */
    public function saveExamDetail()
    {
        $id = $this->request->param('id', 0);
        $data = $this->request->param();
        if (intval($id) === 0) {
            $detail = ExamDetail::create($data)->id;
            $res = ExamDetail::with(['examSecondLevel' => ['examStairType'], 'exam'])->find($detail);
        } else {
            $res = ExamDetail::with(['examSecondLevel' => ['examStairType'], 'exam'])->find($id);
            $res->save($data);
        }
        if (is_null($res)) {
            return $this->response(403, '暂未找到该细则');
        }
        AdminLog::record(intval($id) === 0 ? '新增细则' : '编辑细则', $data, $this->request->uid, $this->request->username);
        return $this->response($res->toArray());
    }

    /**
     * @param $id
     * @User: 刘海龙
     * @Date: 2021/9/27
     * @Time: 9:01
     * @return \think\response\Json
     * @throws \think\db\exception\DataNotFoundException
     * @throws \think\db\exception\DbException
     * @throws \think\db\exception\ModelNotFoundException
     * 预览
     */
    public function previewExam()
    {
        $id = $this->request->param('id', 1);
        $exam = Exam::find(intval($id));
        if (is_null($exam)) {
            return $this->response(403, '暂未找到该问卷');
        }
        $res = ExamDetail::with(['examSecondLevel' => ['examStairType'], 'exam'])->where(['exam_id' => $id])->select()->toArray();
        return $this->response($res);
    }


    /**
     * @User: 刘海龙
     * @Date: 2021/9/27
     * @Time: 10:13
     * @return \think\response\Json
     * @throws \think\db\exception\DataNotFoundException
     * @throws \think\db\exception\DbException
     * @throws \think\db\exception\ModelNotFoundException
     * 更改细则分值
     */
    public function changeExamScore()
    {
        $id = $this->request->param('id');
        $exam_detail = ExamDetail::find($id);
        if (is_null($exam_detail)) {
            return $this->response(403, '暂未找到该细则');
        }
        $type = $this->request->param('type');
        $currentValue = $this->request->param('currentValue');
        if ($type === 'once') { //单次扣分分值
            $meg = '更改单次扣分细则分值';
            $data = [
                'id' => $id,
                'once_deduct_marks' => $currentValue
            ];
        } else if ($type === 'most') { //最大扣分
            $meg = '更改最大扣分细则分值';
            $data = [
                'id' => $id,
                'most_deduct_marks' => $currentValue
            ];
        } else {
            $meg = '';
            $data = [];
        }
        ExamDetail::update($data);
        AdminLog::record($meg, $data, $this->request->uid, $this->request->username);
        return $this->response();
    }

    /**
     * @param $id
     * @User: 刘海龙
     * @Date: 2021/9/27
     * @Time: 10:28
     * @return \think\response\Json
     * @throws \think\db\exception\DataNotFoundException
     * @throws \think\db\exception\DbException
     * @throws \think\db\exception\ModelNotFoundException
     * 问卷细则删除
     */
    public function examDetailDelete($id)
    {
        $exam_detail = ExamDetail::find($id);
        if (is_null($exam_detail)) {
            return $this->response(403, '暂未找到该细则');
        }
        $exam_detail->delete();
        AdminLog::record('删除问卷细则', $id, $this->request->uid, $this->request->username);

        return $this->response();

    }


    /**
     * @User: 刘海龙
     * @Date: 2021/9/26
     * @Time: 17:44
     * @return \think\response\Json
     * 获取类别
     */
    public function getExamType()
    {
        $res = Exam::$is_exam_type;
        return $this->response($res);
    }

    /**
     * @User: 刘海龙
     * @Date: 2021/9/27
     * @Time: 10:28
     * @return \think\response\Json
     * @throws \think\db\exception\DataNotFoundException
     * @throws \think\db\exception\DbException
     * @throws \think\db\exception\ModelNotFoundException
     * 问卷生成 --  手动创建
     */
    public function saveExam()
    {
        $data = $this->request->except(['one_template_id', 'two_template_id']); //试卷数组
        //问卷入库
        $data['create_id'] = $this->request->uid;
        $exam_id = Exam::create($data)->id;
        //获取模版一级分类
        $template_type = TemplateType::with(['templateSecondLevel.templateDetail'])->where([['id', 'in', $this->request->param('one_template_id')]])->select()->toArray();
        foreach ($template_type as $key => $value) {
            //在此新增 一级分类
            $exam_stair_type_id = ExamStairType::create([
                'exam_stair_title' => $value['template_type_title'],
                'year' => $value['year'],
                'exam_id' => $exam_id,
                'create_id' => $this->request->uid
            ])->id;
            foreach ($value['templateSecondLevel'] as $k => $v) {
                if (in_array($v['id'], $this->request->param('two_template_id'))) {
                    $exam_second_level_id = ExamSecondLevel::create([ // 二级
                        'exam_second_title' => $v['second_level_title'],
                        'year' => $v['year'],
                        'exam_id' => $exam_id,
                        'exam_stair_type_id' => $exam_stair_type_id,
                        'create_id' => $this->request->uid
                    ])->id;
                    if (isset($v['templateDetail'])) { //判断是否包含item字段
                        foreach ($v['templateDetail'] as $k1 => $v1) {
                            ExamDetail::create([ // 详情
                                'exam_detail_title' => $v1['template_detail_title'],
                                'year' => $v1['year'],
                                'desc' => $v1['desc'],
                                'deduct_marks_standard' => $v1['deduct_marks_standard'],
                                'once_deduct_marks' => $v1['once_deduct_marks'],
                                'most_deduct_marks' => $v1['most_deduct_marks'],
                                'exam_id' => $exam_id,
                                'exam_stair_type_id' => $exam_stair_type_id,
                                'exam_second_level_id' => $exam_second_level_id,
                                'create_id' => $this->request->uid
                            ]);
                        }
                    }
                }
            }
        }


        AdminLog::record('生成问卷', $data, $this->request->uid, $this->request->username);
        return $this->response();
    }


    /**
     * @param $id
     * @User: 刘海龙
     * @Date: 2021/9/27
     * @Time: 14:32
     * @return \think\response\Json
     * @throws \think\db\exception\DataNotFoundException
     * @throws \think\db\exception\DbException
     * @throws \think\db\exception\ModelNotFoundException
     * 删除问卷
     */
    public function examDelete($id)
    {
        $res = Exam::with(['examStairType', 'examSecondLevel', 'examDetail'])->find($id);
        if (is_null($res)) {
            return $this->response(403, '暂未找到该问卷');
        }
        $res->together(['examStairType', 'examSecondLevel', 'examDetail'])->force()->delete();
        AdminLog::record('删除问卷', $id, $this->request->uid, $this->request->username);
        return $this->response();
    }


    /**
     * @User: 刘海龙
     * @Date: 2021/9/27
     * @Time: 15:26
     * @return \think\response\Json
     * @throws \think\db\exception\DataNotFoundException
     * @throws \think\db\exception\DbException
     * @throws \think\db\exception\ModelNotFoundException
     * 发布and撤回
     */
    public function examReleaseAndWithdraw()
    {
        $id = $this->request->param('id', 0);
        $old_release = $this->request->param('old_release');
        $res = Exam::find($id);
        if (is_null($res)) {
            return $this->response(403, '暂未找到该问卷');
        }
        $res->save([
            'id' => $id,
            'is_release' => $old_release === Exam::IS_RELEASE_ONE ? Exam::IS_RELEASE_ZERO : Exam::IS_RELEASE_ONE
        ]);
        AdminLog::record($old_release === Exam::IS_RELEASE_ONE ? '撤回问卷' : '发布问卷', $this->request->param(), $this->request->uid, $this->request->username);
        return $this->response();
    }


    /**
     * @User: 刘海龙
     * @Date: 2021/9/27
     * @Time: 17:59
     * @return \think\response\Json
     * @throws \think\db\exception\DataNotFoundException
     * @throws \think\db\exception\DbException
     * @throws \think\db\exception\ModelNotFoundException
     * 随机and全部
     */
    public function saveExamRandomAndAll()
    {
        $data = $this->request->param();
        $data['create_id'] = $this->request->uid;
        $exam_id = Exam::create($data)->id;
//        if ($data['type'] === 'random') { //随机
//            $disposeData = Template::randomTemplate($data['exam_template_id'], 3,$data['type']);
//        } else { //全部
//            $disposeData = Template::templateAllCreate($data['exam_template_id']);
//        }
        $disposeData = Template::randomTemplate($data['exam_template_id'], 3, $data['type']);
        if ($disposeData['code'] === 200) {
            $is_result = Exam::synchronousData($disposeData, $exam_id, $this->request->uid);
            if ($is_result === 200) {
                return $this->response();
            } else {
                // 真实删除
                Exam::destroy($exam_id, true);
                return $this->response(403, '处理数据失败');
            }
        } else {
            // 真实删除
            Exam::destroy($exam_id, true);
            return $this->response($disposeData['code'], $disposeData['msg']);
        }
    }

    /**
     * Notes:
     * User: liuhailong
     * DateTime: 2022/9/19 10:13
     * @return \think\response\Json
     * 未上传      问卷记录表
     */
    public function notUploadExam()
    {
        $data = $this->request->param();
        if (!empty($data['img_path'])) {
            $data['img_json'] = json_encode($data['img_path'], JSON_UNESCAPED_SLASHES | JSON_UNESCAPED_UNICODE);
        }
        $data['user_id'] = $this->request->wx_id;
        $data['unit_id'] = $this->request->wx_unit_id;
        $not_id = NotUploadQuestion::create($data)->id;
        if ($not_id > 0) {
            $parent_arr = $this->search->getParent($data['unit_id']);

            //新增日志表
            NotUploadQuestionLog::create([
                'not_upload_question_id' => $not_id,
                'parent_unit_id' => $parent_arr[0]['id'],
                'status' => 1 // 未审核
            ]);
        }
        return $this->response();

    }

    /**
     * Notes:
     * User: liuhailong
     * DateTime: 2022/9/20 10:15
     * @return \think\response\Json
     * @throws \think\db\exception\DataNotFoundException
     * @throws \think\db\exception\DbException
     * @throws \think\db\exception\ModelNotFoundException
     * 替换人员
     */
    public function replaceUserExam(){
        $old_user_id = $this->request->param('old_user_id');
        $old_unit_id = $this->request->param('old_unit_id');
        $is_find_user = Users::where(['username'=>$this->request->param('username'),'mobile'=>$this->request->param('mobile')])->find();
        if (is_null($is_find_user)) {
            return $this->response(404, '未找到该用户名为'.$this->request->param('username').'的用户');
        }
        $new_user_id = $is_find_user['id'];
        $new_unit_id = $is_find_user['unit_id'];
        //1.查询用户
        $user = Users::withTrashed()->field('id,username,nickname,head_img,unit_id,is_admin')->find($old_user_id);
        //1.1 判断用户是否为空 为空直接返回
        if (is_null($user)) {
            return $this->response(404, '未找到该用户');
        }
        //2.查询恢复前每日答题的表[topic_user_day]  条件为网点id 及用户id
        $topic_user_day_res = TopicUserDay::withTrashed()->where(['unit_id' => $old_unit_id])->where('user_id', $old_user_id)->select();
        //2.1判断是否为空
        if (!$topic_user_day_res->isEmpty()) {
            //2.1.1不为空的时候进行循环恢复数据
            foreach ($topic_user_day_res as $key => $v) {
                $topicUserDay = TopicUserDay::withTrashed()->find($v['id']);
                //2.1.2恢复数据
                $topicUserDay->restore();
                // 2.1.3 恢复数据后进行更新为新的网点信息
                $topicUserDay->save(['user_id' => $new_user_id,'unit_id' => $new_unit_id]);

            }
        }
        //3.查询每日答题同步表[topic_user_day_sync] 条件为网点id 及用户id
        $topic_user_day_sync_res = TopicUserDaySync::withTrashed()->where(['unit_id' => $old_unit_id])->where('user_id', $old_user_id)->select();
        //3.1判断是否为空
        if (!$topic_user_day_sync_res->isEmpty()) {
            //3.1.1不为空的时候进行循环恢复数据
            foreach ($topic_user_day_sync_res as $key1 => $v1) {
                $topic_user_day_sync = TopicUserDaySync::withTrashed()->find($v1['id']);
                //3.1.2恢复数据
                $topic_user_day_sync->restore();
                // 3.1.3恢复数据后进行更新为新的网点信息
                $topic_user_day_sync->save(['user_id' => $new_user_id,'unit_id' => $new_unit_id]);

            }
        }

        //4.总人数
        $persons_total = Users::where('unit_id', $new_unit_id)->count();
        //5.答题人数 [3,4] 均为可答题人员
        $user_total = Users::where('unit_id', $new_unit_id)->whereIn('wx_role_id', [3, 4])->count();
        //6.查询单位总数表[unit_total] 条件为网点id
        $unit_total_res_restore = UnitTotal::where(['unit_id' => $new_unit_id])->findOrEmpty();
        //6.1 判断是否为空
        if (!$unit_total_res_restore->isEmpty()) {
            $unit_total_res_restore->save([
                'persons_total' => $persons_total,
                'answer_persons_total' => $user_total,
            ]);
        }
        //7.每日答题统计答题网点是否完成答题表[every_day_answer_census]  whereFindInSet 查询当前user_ids中是否包含该用户 条件为网点id 及用户id
        $every_day_answer_census_res = EveryDayAnswerCensus::withTrashed()->where(['unit_id' => $new_unit_id])->select();
        //7.1 为空的时候 把原有的值更改为现有的总数
        if ($every_day_answer_census_res->isEmpty()) {
            $list = EveryDayAnswerCensus::where(['unit_id' => $new_unit_id])->select();
            if (!$list->isEmpty()) {
                $list->update(['unit_number' => $user_total]);
            }
        } else {
            //7.2 不为空的时候
            foreach ($every_day_answer_census_res as $k => $v2) {
                //7.2.1 查询当前删除信息的数据
                $every_day = EveryDayAnswerCensus::withTrashed()->find($v2['id']);

                //7.2.2 查询当前删除的信息进行恢复
                $every_day->restore();
                //7.2.3 查询当前日期该用户是否答题了 如果答题 进行合并user_ids

                $is_dt = TopicUserDay::where(['date_of' => $v2['date_of'], 'user_id' => $new_user_id])->findOrEmpty();

                //7.2.3.1 不为空的时候 user_ids 进行拼接更新

                $new_user_ids = "";
                if (!$is_dt->isEmpty()) {
                    $new_user_ids = $new_user_id;
                }

                //7.2.3.1.1 转为数组
                $is_user_id_arr = explode(',', $every_day['user_ids']);

                //判断数组是否包含 $data['user_id']
                if (!in_array($new_user_ids, $is_user_id_arr)) {
                    //7.2.3.2 新的数组user_ids 字符串
                    $new_user_ids_arr = $every_day['user_ids'] . ',' . $new_user_ids;
                } else {
                    $new_user_ids_arr = $every_day['user_ids'];
                }
                //7.2.4 user_ids 转为数组
                $user_id_arr = explode(',', $new_user_ids_arr);
                //7.2.4.1 更新
                $every_day->save([
                    'completed_number' => count($user_id_arr),
                    'unit_number' => $user_total,
                    'user_ids' => rtrim($new_user_ids_arr, ",") //去除最后一个逗号
                ]);
            }
        }
        //8.1 更新以外的数据总数
        EveryDayAnswerCensus::where('unit_id', $new_unit_id)->update([
            'unit_number' => $user_total,
        ]);

        return $this->response();

    }
}
